# coding=utf-8
"""
    flask route
"""
import io
import base64
import uuid

import logging
import requests
import paddleocr
from paddleocr import draw_ocr
from flask import Blueprint, request, current_app
from PIL import Image
import numpy as np

from utils.base.base_res import base_res

# @Time    :  2024-10-29 17:11:58
# @Author  :  jiangtong
# @Email   :  gingerqgyy@outlook.com
# @Project :  flask_ocr
# @File    :  ocr

logging.basicConfig(level=logging.ERROR)

# 创建蓝图实例 :
ocr_bp = Blueprint('ocr_bp', __name__)

# 初始化 PaddleOCR :
ocr = paddleocr.PaddleOCR(use_angle_cls=True, lang='ch')


# 图片 ocr 识别 :
def process_image(image_data):
    """ 处理图像并返回识别结果 """
    # 将 PIL.Image.Image 对象转换为 numpy 数组
    image_array = np.array(image_data)
    # ocr 识别 :
    result = ocr.ocr(image_array, cls=True)
    return result


# 图片方向识别 :
def image_angle(image_data):
    """ 方向识别 """
    # 将 PIL.Image.Image 对象转换为 numpy 数组
    image_array = np.array(image_data)
    result = ocr.ocr(image_array[0], det=False, rec=False, cls=True)
    return result


@ocr_bp.route('/ocr', methods=['POST'])
def ocr_api():
    url = request.json.get('url')
    current_app.logger.info(f'图片来源 : {url}')
    trace_id = str(uuid.uuid4())
    if not url:
        return base_res(code='DATA_VALIDATION_FAILED', message='The given url must not be null!', trace_id=trace_id)
    try:

        response = requests.get(url)
        current_app.logger.debug(f'提取图片链接成功')
        response.raise_for_status()

        # 将下载的图像数据转换为 PIL.Image.Image 对象
        image = Image.open(io.BytesIO(response.content))
        current_app.logger.debug(f'图片转为 Image 对象成功')

        # 格式处理 : ( 确保图像模式为 RGB )
        if image.mode != 'RGB':
            image = image.convert('RGB')

        # 处理图像并返回识别结果
        result = process_image(image)
        if not result:
            return base_res(code='INTERNAL_SERVER_ERROR', message=f'图像识别异常', trace_id=trace_id)
        current_app.logger.debug(f'图像识别成功 -> result : < {result} >')

        boxes = [line[0] for line in result[0]]

        # 处理识别结果

        # 绘制 OCR 结果
        # """
        # im_show = draw_ocr(image, boxes, txts=None, scores=None, font_path='./fonts/simfang.ttf')
        im_show = Image.fromarray(draw_ocr(image, boxes, txts=None, scores=None, font_path='./fonts/simfang.ttf'))
        current_app.logger.debug(f'图像绘制成功')

        # 将 im_show 转换为 RGB 模式 ( 去除透明通道 )
        if im_show.mode == 'RGBA':
            im_show = im_show.convert('RGB')

        # 将绘制后的图像转换为 base64 字符串
        buffered = io.BytesIO()
        # Image.fromarray(im_show).save(buffered, format="JPEG")
        im_show.save(buffered, format="JPEG")
        im_base64 = base64.b64encode(buffered.getvalue()).decode('utf-8')
        current_app.logger.debug(f'图像绘制并转换成功')

        # 将图片保存本地 : ( 调试时可以保存下, 能看见图片 )
        # im_show.save('aaa.jpeg', format="JPEG")
        # current_app.logger.debug(f'{trace_id} -> 图片保存本地成功')
        # """
        return base_res(result={'result': result[0], 'image': im_base64}, trace_id=trace_id)
    except requests.exceptions.HTTPError as e:
        current_app.logger.exception(e)
        return base_res(code='RESOURCE_VALIDATION_FAILED', message=f'图片链接有误', error_code=f'{e}', trace_id=trace_id)
    except requests.exceptions.SSLError as e:
        current_app.logger.exception(e)
        return base_res(code='INTERNAL_SERVER_ERROR', message=f'阿里云 OSS 访问受限', error_code=f'{e}', trace_id=trace_id)
    except Exception as e:
        current_app.logger.exception(e)
        return base_res(code='INTERNAL_SERVER_ERROR', message=f'系统未知异常!', error_code=f'{e}', trace_id=trace_id)
